using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.InputSystem;

public class PlayerDashState : PlayerGroundedState
{
    private DashData dashData;
    private float startTime;
    private int dashAmount;

    private bool shouldKeepRotating;

    public PlayerDashState(PlayerMovementMachine stateMachine) : base(stateMachine)
    {
        dashData = stateMachine.Player.Data.PlayerGroundedData.DashData;
    }

#region IState Methods
    public override void Enter()
    {
        base.Enter();

        StartAnimation(StateMachine.Player.AnimationData.DashParameterHash);

        StateMachine.ReusableData.MovementSpeedModify = dashData.SpeedModify;
        StateMachine.ReusableData.CurrentJumpForce = airborneData.JumpData.StrongForce;


        StateMachine.ReusableData.RotationData = dashData.RotationData;
        shouldKeepRotating = StateMachine.ReusableData.InputMovement != Vector2.zero;
        
        AddForceOnTransitionFromStationaryState();

        UpdateConsecutiveData();

        startTime = Time.time;
    }

    public override void PhysicUpdate()
    {
        base.PhysicUpdate();

        if (!shouldKeepRotating)
            return;
        
        RotateTowardsTargetRotation();
    }

    public override void Exit()
    {
        base.Exit();
        SetBaseRotation();
        StopAnimation(StateMachine.Player.AnimationData.DashParameterHash);
    }

    public override void OnAnimationTransitionEvent()
    {
        if (StateMachine.ReusableData.InputMovement == Vector2.zero)
        {
            StateMachine.ChangeState(StateMachine.HardStoppingState);
            return;
        }
            
        StateMachine.ChangeState(StateMachine.SprintingState);
    }

    protected override void AddInputActionsCallBacks()
    {
        base.AddInputActionsCallBacks();
        StateMachine.Player.PlayerInput.PlayerActions.Movement.performed += MovementOnperformed;
    }

    protected override void RemoveInputActionsCallBacks()
    {
        base.RemoveInputActionsCallBacks();
        StateMachine.Player.PlayerInput.PlayerActions.Movement.performed -= MovementOnperformed;

    }
#endregion

#region Main Methods
    private void AddForceOnTransitionFromStationaryState()
    {
        if (StateMachine.ReusableData.InputMovement == Vector2.zero)
            return;

        Vector3 characterDir = StateMachine.Player.transform.forward;
        characterDir.y = 0;

        UpdateTargetRotation(characterDir, false);
        
        StateMachine.Player.Rigidbody.velocity = characterDir * GetMovementSpeed();
    }

    private void UpdateConsecutiveData()
    {
        if (!IsConsecutive())
        {
            dashAmount = 0;
        }

        dashAmount++;

        if (dashAmount >= dashData.DashLimitAmount)
        {
            dashAmount = 0;
            StateMachine.Player.PlayerInput.SetActionDisableForSeconds(
                StateMachine.Player.PlayerInput.PlayerActions.Dash, dashData.DashCoolDown);
        }
    }

    private bool IsConsecutive()
    {
        return Time.time < startTime + dashData.TimeToBeConsideredConsecutive;
    }
#endregion

#region Input Methods
    protected override void OnMovementCanceled(InputAction.CallbackContext context)
    {
    }

    private void MovementOnperformed(InputAction.CallbackContext obj)
    {
        shouldKeepRotating = true;
    }
    
    protected override void OnDashStarted(InputAction.CallbackContext context)
    {
    }
#endregion
}